package com.ballaci.google.wave.robot;

import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.net.URLEncoder;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.regex.PatternSyntaxException;

import com.google.wave.api.AbstractRobotServlet;
import com.google.wave.api.Blip;
import com.google.wave.api.Element;
import com.google.wave.api.Event;
import com.google.wave.api.EventType;
import com.google.wave.api.Image;
import com.google.wave.api.RobotMessageBundle;
import com.google.wave.api.TextView;
import com.google.wave.api.Wavelet;

public class UrlFreezerServlet extends AbstractRobotServlet {

	@Override
	public void processEvents(RobotMessageBundle bundle) {
		Wavelet wavelet = bundle.getWavelet();

		if (bundle.wasSelfAdded()) {
			Blip blip = wavelet.appendBlip();
			TextView textView = blip.getDocument();
			textView.append("Hello from UrlFreezer! write [url] in order to freeze that page for future reference! for more info go to http://www.webcitation.org/");
		}

		getServletContext().log("wavelet called! id: " + wavelet.getWaveletId() + " title: "
				+ wavelet.getTitle());
		for (Event e : bundle.getEvents()) {
			if (e.getType() == EventType.BLIP_SUBMITTED) {
				Blip blip = e.getBlip();
				TextView convertedText = blip.getDocument();
				convertedText = convertText(blip);
			}
		}
	}

	public TextView convertText(Blip blip) {
		String error = "error: unable to freeze url, will retry on the next submit!";
		String initialText = blip.getDocument().getText();
		getServletContext().log("initial text: " + initialText);
		StringBuffer result = new StringBuffer(); 
		String noErrors = cleanPreviousErrors(initialText);
		getServletContext().log("noErrors: " + noErrors);
		Pattern p = Pattern.compile("\\[(http://)?[a-zA-Z_0-9\\-]+(\\.\\w[a-zA-Z_0-9\\-]+)+(/[&amp;\\n\\-=?\\+\\%/\\.\\w]+)?\\]");
		Matcher m = p.matcher(noErrors);
		String frozenUrl = null;
		while (m.find()) {
			String href = m.group();
			if(href == null) break;
			href = href.replace("[","");
			href = href.replace("]","");
			String citeResponse = archiveCite(href, blip.getCreator());
			frozenUrl = stripFrozenUrl(citeResponse);
			if (frozenUrl != null) {
				logCall(href, blip.getCreator(), 0);
				m.appendReplacement(result, frozenUrl);
			}else{
				logCall(href, blip.getCreator(), 1);
				String message = "["+ href + "] " + error;
				m.appendReplacement(result, message);
			}
		}
		m.appendTail(result);
		TextView newView = blip.getDocument();
		newView.replace(result.toString());
		Element img = new Image();
		img.setProperty("url", "http://urlfreezer.appspot.com/_wave/robot/webcite.gif");
		if(frozenUrl != null)newView.insertElement(result.indexOf(frozenUrl) + frozenUrl.length(), img);    //Add Image
		return newView;
	}

	private String archiveCite(String href, String creator) {
		creator = creator.substring(0, creator.indexOf("@")) + "@gmail.com";
		String webCiteArchive = "http://www.webcitation.org/archive.php?url=" + href + "&email=" + creator;
		getServletContext().log("archive url to call: " + webCiteArchive);
		String citeResponse = UrlFetcher.fetchUrl(webCiteArchive);
		getServletContext().log("archive response: " + citeResponse);
		return citeResponse;
	}
	
	private String stripFrozenUrl(String resp) {
		if (resp == null) return null;
		String citeUrl = null;
		Pattern p = Pattern.compile("(http://www.webcitation.org/)+[a-zA-Z_0-9]+(\\)</a></font></p>)");
		Matcher m = p.matcher(resp);
		while (m.find()) {
			 citeUrl = m.group();
		}
		getServletContext().log("citeUrl: " + citeUrl);
		return (citeUrl != null) ? citeUrl.substring(0, citeUrl.indexOf(")")) : citeUrl;
	}
	
	private String cleanPreviousErrors(String initialText){
		StringBuffer sb = new StringBuffer(); 
		try {
			Pattern regex = Pattern.compile("error:\\ unable\\ to\\ freeze\\ url,\\ will\\ retry\\ on\\ the\\ next\\ submit!");
			Matcher regexMatcher = regex.matcher(initialText);
			while (regexMatcher.find()) {
				String error = regexMatcher.group();
				if(error != null) regexMatcher.appendReplacement(sb, ""); //clean message errors
			} 
			regexMatcher.appendTail(sb);
		} catch (PatternSyntaxException ex) {
			// Syntax error in the regular expression
		}
		return sb.toString();
	}
	
	private void logCall(String href, String email, int esito){
		try {
			String weblogUrl ="http://www.ballaci.com/weblog/url_freezer.php?esito="+ esito +"&url=" + href + "&email=" + email;
			UrlFetcher.fetchUrl(weblogUrl);
			getServletContext().log("logging call: " + weblogUrl);
		} catch (Exception e) {
			getServletContext().log("Exception: " + href + " email:" + email);
		} 
	}
}
